class Promise{
    constructor(executor){
        this.PromiseState='pending'; //默认初始化时就是pending状态
        this.PromiseResult=null;  //返回的内容
        this.callbacks=[];
        const self=this;
        function resolve (val){
            if(self.PromiseState !=='pending') return;
            self.PromiseState='fulfilled';
            self.PromiseResult=val;
            self.callbacks.forEach(element => {
                element.onFulfilled();
            });
        }
    
        //箭头函数中的定义，如果形式参数只有一个，那么是可以省略小括号的
        const reject= val=>{
            if(this.PromiseState !=='pending') return;
            this.PromiseState='rejected';
            this.PromiseResult=val;
            this.callbacks.forEach(element => {
                element.onRejected();
            });
        }
        try{
            executor(resolve,reject);
        }catch(ex) {
            reject(ex);
        }
    }

    then(onResolved, onRejected){
        const self= this;
        if(!(onResolved instanceof Function)){ onResolved= val =>val;}
        if(!(onRejected instanceof Function)){onRejected= reason=> {throw reason}}       
        return new Promise((resolve,reject)=>{
            //封装函数
            function myCallback(typeMethod){
                setTimeout(() => {
                    try{
                        let result= typeMethod (self.PromiseResult);
                        if(result instanceof Promise){
                            result.then(v=>{ resolve(v)},r=>{ reject(r)})
                        }else{
                            resolve(result);
                        }
                    }catch(ex){
                        reject(ex);
                    }
                });
            }
            if(this.PromiseState==='fulfilled'){
               myCallback(onResolved);
    
            }else if(this.PromiseState==='rejected'){
                myCallback(onRejected);
            }else{ //状态为 pending
                this.callbacks.push({
                    onFulfilled:function(){
                        myCallback(onResolved);
                    },
                    onRejected:function(){
                        myCallback(onRejected); 
                    }
                })
            }
        })
    }

    catch(onRejected){
        return this.then(undefined,onRejected);
    }

    static resolve(val){
        return new Promise((resolve,reject)=>{
            if(val instanceof Promise){
                val.then(v=>{ resolve(v)},r=>{reject(r)})
            }else{
                resolve(val);
            }
        })
    }

    static reject(val){
        return new Promise((resolve,reject)=>{
            reject(val);
        })
    }

    static all(promises){
        return new Promise((resolve,reject)=>{
            let arr=[];
            for(let i=0; i< promises.length; i++){
                promises[i].then(v=>{
                    arr[i]=v;
                },r=>{
                    reject(r);
                })
            }
            resolve(arr);
        }) 
    }

    static race(promises){
        return new Promise((resolve,reject)=>{
            for(let i=0; i< promises.length; i++){
                promises[i].then(v=>{
                    resolve(v);
                },r=>{
                    reject(r);
                })
            }
        });
    }
}